﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using OpcUaHelper;

namespace Forging2.Services.OPCService
{
    class OpcUaClientServer
    {
        public OpcUaHelper.OpcUaClient OpcUaClient;        
        public OpcUaClientServer()
        {
            OpcUaClient = new OpcUaClient();
           
        }

        public void OpenOPCServer(string opcURL)
        {
            OpcUaClient.ConnectServer(opcURL);
        }

        public void Subscription(string[] NodeIds,Action<string,Opc.Ua.Client.MonitoredItem,Opc.Ua.Client.MonitoredItemNotificationEventArgs> subcallback)
        {
            OpcUaClient.AddSubscription(Environment.MachineName, NodeIds, subcallback);
        }
        public void Subscription(string[] NodeIds)
        {
            OpcUaClient.AddSubscription(Environment.MachineName, NodeIds, SubCallback);
        }
        private void SubCallback(string key, Opc.Ua.Client.MonitoredItem monitoredItem, Opc.Ua.Client.MonitoredItemNotificationEventArgs args)
        {
            Console.WriteLine($"{key}  {monitoredItem.StartNodeId.ToString() }  {args.NotificationValue.ToString()}  ");
        }

        public void RemoveSubscription()
        {
            OpcUaClient.RemoveAllSubscription();
        }
        public void CloseOPCServer()
        {
            OpcUaClient.Disconnect();
        }
        /// <summary>
        /// 异步读取PLC地址
        /// </summary>
        /// <param name="nodeid">节点名称</param>
        /// <param name="type">读取数据类型0-bool，1-short，2-int，3-uint32，4-float，5-decimal，6-double，10-string</param>       
        /// <returns></returns>
        public async Task<dynamic> ReadValueAsync(string nodeid,int type)
        {
            switch (type)
            {
                case 0:
                    return await OpcUaClient.ReadNodeAsync<bool>(nodeid);
                case 1:
                    return await OpcUaClient.ReadNodeAsync<short>(nodeid);
                case 2:
                    return await OpcUaClient.ReadNodeAsync<int>(nodeid);
                case 3:
                    return await OpcUaClient.ReadNodeAsync<UInt32>(nodeid);
                case 4:
                    return await OpcUaClient.ReadNodeAsync<float>(nodeid);
                case 5:
                    return await OpcUaClient.ReadNodeAsync<decimal>(nodeid);
                case 10:
                    return await OpcUaClient.ReadNodeAsync<string>(nodeid);
                default:
                    return await OpcUaClient.ReadNodeAsync<string>(nodeid);
            }            
        }
        /// <summary>
        /// 异步写入PLC地址
        /// </summary>
        /// <param name="nodeid">节点名称</param>
        /// <param name="type">写入数据类型0-bool，1-short，2-int，3-uint32，4-float，5-decimal，6-double，10-string</param>
        /// <param name="value">写入值</param>
        /// <returns></returns>
        public async Task<bool> WriteValueAsync(string nodeid,int type,dynamic value)
        {
            switch (type)
            {
                case 0:
                   return await OpcUaClient.WriteNodeAsync<bool>(nodeid, value);
                case 1:
                    return await OpcUaClient.WriteNodeAsync<short>(nodeid, value);
                case 2:
                    return await OpcUaClient.WriteNodeAsync<int>(nodeid, value);
                case 3:
                    return await OpcUaClient.WriteNodeAsync<UInt32>(nodeid, value);
                case 4:
                    return await OpcUaClient.WriteNodeAsync<float>(nodeid, value);
                case 5:
                    return await OpcUaClient.WriteNodeAsync<decimal>(nodeid, value);
                case 6:                
                    return await OpcUaClient.WriteNodeAsync<double>(nodeid, value);
                case 10:
                    return await OpcUaClient.WriteNodeAsync<string>(nodeid, value);
                default:
                    return await OpcUaClient.WriteNodeAsync<bool>(nodeid, value);

            }
        }
    }
}
